(function(fw) {

	var Guide = function(tourSteps, options, currentStep) {
		setDefaultTemplate();
		var self = this,
			defaults = {
				previousButton: false,
				nextButtonText: '下一步',
				endTourButtonText: '完成',
				previousButtonText: '上一步',
				template: defaultTourGuideTemplate,
				customCSS: 'tour-guide-popover'
			},
			template,
			options = options || {},
			tourSteps = tourSteps || [],
			currentStep = currentStep || 0;

		function setDefaultTemplate() {
			defaultTourGuideTemplate = '<div class="popover popover-step-tutorial {{#if options.customCSS}}{{options.customCSS}}{{/if}}">' +
				'<div class="popover-angle"></div>' +
				'<div class="popover-inner">' +
				'<div class="tour-guide-container-wrapper">' +
				'<div class="tour-guide-header-wrapper"><p class="tour-guide-header">{{header}}</p></div>' +
				'<div class="tour-guide-message-wrapper"><p class="tour-guide-message">{{message}}</p></div>' +
				'</div>' +
				'<div class="tour-guide-toolbar-wrapper">' +
				'<div class="toolbar">' +
				'<div class="toolbar-inner">' +
				'<div class="row tour-guide-buttons-row">' +
				'{{#if options.previousButton}}' +
				'<div class="col-50">' +
				'<a href="#" class="button button-fill tour-guide-button tour-guide-previous-button" {{#unless options.enablePreviousButton}}disabled="disabled"{{/unless}}>{{options.previousButtonText}}</a>' +
				'</div>' +
				'{{/if}}' +
				'<div class="col-{{#if options.previousButton}}50{{else}}100{{/if}}">' +
				'<a href="#" class="button button-fill tour-guide-button tour-guide-next-button">{{#if options.lastStep}}{{options.endTourButtonText}}{{else}}{{options.nextButtonText}}{{/if}}</a>' +
				'</div>' +
				'</div> ' +
				'</div>' +
				'</div>' +
				'</div>' +
				'</div>' +
				'</div>';
		};

		self.setMoveForwardAction = function() {
			$(document).on('click', '.tour-guide-next-button', function(e) {
				e.preventDefault();
				e.stopImmediatePropagation();
				e.stopPropagation();

				currentStep++;

				if(tourSteps.length === currentStep) {
					console.log('No more steps');
				} else {
					console.log('Next step');
				}

				self.showTour(tourSteps, currentStep);
			});
		};

		self.setMoveBackwardAction = function() {
			$(document).on('click', '.tour-guide-previous-button', function(e) {
				e.preventDefault();
				e.stopImmediatePropagation();
				e.stopPropagation();
				console.log('previous step');

				currentStep--;

				self.showTour(tourSteps, currentStep);
			});
		};

		self.moveFoward = function() {
			if(+currentStep === tourSteps.length) {
				console.log('Last step, cannot move forward.');
				return;
			}

			currentStep++;

			if(tourSteps.length === currentStep) {
				console.log('No more steps');
			} else {
				console.log('Next step');
			}

			self.showTour(tourSteps, currentStep);
		};

		self.moveBackward = function() {
			if(+currentStep === 0) {
				console.log('First step, cannot move backwards.');
				return;
			}

			currentStep--;

			if(tourSteps.length === currentStep) {
				console.log('No more steps');
			} else {
				console.log('Next step');
			}

			self.showTour(tourSteps, currentStep);
		};

		self.showTour = function() {
			setTimeout(function() {
				try {
					// close previous modal if exists
					app.popover.close();

					// terminate tour
					if(currentStep === (tourSteps.length)) {
						if(typeof tourSteps[currentStep] !== 'undefined' &&
							tourSteps[currentStep] !== null &&
							typeof tourSteps[currentStep].action !== "undefined" &&
							tourSteps[currentStep].action !== null &&
							typeof tourSteps[currentStep].action === "function") {
							tourSteps[currentStep].action();
						}

						currentStep = 0;

						return;
					}

					if(typeof tourSteps[currentStep].action !== "undefined" &&
						tourSteps[currentStep].action !== null &&
						typeof tourSteps[currentStep].action === "function") {
						tourSteps[currentStep].action();
					}

					/*
					 * popover arguments:
					 *  - tourStep html
					 *  - tourStep element
					 *  - removeOnClose
					 *  - animated
					 *  - closeByOutside
					 */
					var dynamicPopover = app.popover.create({
						closeByOutsideClick:false,
						closeByBackdropClick:false,
						targetEl: tourSteps[currentStep].element,
						content:tourSteps[currentStep].html,
						on: {
							open: function(popover) {
							},
							opened: function(popover) {
							},
						}
					});
					dynamicPopover.open();
				} catch(framework7NotReadyException) {
					console.log("Framework7 is not ready yet");
					console.log(framework7NotReadyException);
				}
			}, 100);
		};

		function applyOptions() {
			var def;
			options = options || {};
			for(def in defaults) {
				if(typeof options[def] === 'undefined') {
					options[def] = defaults[def];
				}
			}
		}

		function compileTemplate() {
			if(!options.template) {
				if(!app.tourguide) {
					app.tourguide = Template7.compile(defaultTourGuideTemplate);
				}
				template = app.tourguide;
			} else {
				template = Template7.compile(options.template);
			}
		}

		self.prepareSteps = function() {
			for(var step in tourSteps) {
				var context = {};

				if(tourSteps[step].header) {
					context.header = tourSteps[step].header;
				}

				if(tourSteps[step].message) {
					context.message = tourSteps[step].message;
				}

				if(options.previousButton &&
					step > 0) {
					options.enablePreviousButton = true;
				}

				if(+step === tourSteps.length - 1) {
					options.lastStep = true;
				}

				context.options = options;

				try {
					tourSteps[step].html = template(context);
				} catch(TemplateNotDefinedException) {
					console.log('Failed to compile template with context');
					console.log(TemplateNotDefinedException);
				}
			}
		};

		(function() {
			setDefaultTemplate();
			compileTemplate();
			applyOptions();
			self.prepareSteps();
			self.setMoveForwardAction();
			self.setMoveBackwardAction();

		}());

		return self;
	};

	fw.guide = function(steps, options, currentStep) {
		return new Guide(steps, options, currentStep);
	};

})(window.framework);